package source.Objetos 
{
    import flash.geom.Point;
    import net.flashpunk.graphics.Image;
    import net.flashpunk.masks.Pixelmask;
    import source.Assets;
    import source.Global;

	public class Proyectil extends Physics {
		public var delPJ:Boolean;                      //indica que es un proyectil disparado por el PJ y no por cualquier enemigo
		public var velocidad:Point;                    //vector en forma binomial
		public var tieneMasa:Boolean;                  //true = le afecta la gravedad, false = seguirá una línea recta
		public var tiempoVida:int = Global.proy_tiempoVida; //timer que pone una "caducidad" al proyectil. Por protección ante "flooding" de proyectiles
		
        /**
         * Constructor
         * @param	x: coordenada 'x' de la posición del proyectil
         * @param	y: coordenada 'y' de la posición del proyectil
         * @param	_tieneMasa: true si le afecta la gravedad
         * @param	_velocidadMod: módulo del vector que describe su velocidad inicial
         * @param	_velocidadArg: argumento del vector que describe su velocidad inicial
         * @param	_delPJ: true si el proyectil ha sido disparado por el PJ
         * @param	_grafico: cadena de texto para indicar qué gráfico ha de tener
         */
		public function Proyectil(x:int, y:int, _velocidadMod:Number, _velocidadArg:Number, _tieneMasa:Boolean, _delPJ:Boolean, _grafico:String) {
            //Posicionamos la entidad:
			super(x, y);
            
            //Gráfico y Hitbox:
            switch (_grafico) {
                case "pj":
                    graphic = new Image(Assets.PROY_PJ);
                    mask = new Pixelmask(Assets.PROY_PJ);
                    break;
                case "1":
                    graphic = new Image(Assets.PROY_ENEM01);
                    mask = new Pixelmask(Assets.PROY_ENEM01);
                    break;
                case "singrafico":
                default:
                    graphic = new Image(Assets.PROY_ENEM00);
                    mask = new Pixelmask(Assets.PROY_ENEM00);
            }
			
			delPJ = _delPJ;
			velocidad = obtenerCartesianas(_velocidadMod, _velocidadArg);
			tieneMasa = _tieneMasa;
            
            if (delPJ) type = "ProyectilPJ";
            else type = "Proyectil";
			
            //Gestión de la gravedad según si el proyectil se mueve en el agua o en el aire y si tiene masa:
            if (tieneMasa) {
                if (collide("Agua", x, y)) mGravity = Global.gravedad_enAgua * Global.proy_factorGravedad;
                else mGravity = Global.gravedad_enAire * Global.proy_factorGravedad;
            }
			else
                mGravity = 0;
            
			speed = mMaxspeed = velocidad;
            
            //Si el proyectil es de un enemigo, lo hacemos invisible y "fantasmal", ya que las coordenadas que nos han dado
            //como parámetros del constructor son el centro del enemigo, y hasta que no dejen de solaparse no debería ni verse
            //ni desaparecer debido a la colisión:
            if (!delPJ) {
                type = "fantasma";
                visible = false;
            }
		}
		
        /**
         * update
         * Es llamado cada frame
         */
		override public function update():void {
            //Si el pj está muerto o se está teletransportando, los proyectiles se paralizan y no hacen nada:
            if (Global.pj.muerto || Global.salirPantalla_porTeletransporte) return;
            
			motion();
            if (tieneMasa) {
                gravity();
                gravity();
                gravity();
            }
            
            //Si el proyectil es tiene type="fantasma" quiere decir que es un proyectil de un enemigo que acaba de ser
            //disparado desde su interior, por lo que se solapan y hay colisión. Cuando deje de haberla, le cambiamos
            //a type="Proyectil" y le hacemos visible:
            if (type == "fantasma") {
                if (!collide("Enemigo", x, y) && !collide("EnemigoInofensivo", x, y)) {
                    type = "Proyectil";
                    visible = true;
                }
            }
            //Si no es de type="fantasma", actuamos normalmente:
            else {
                if (collide("Enemigo", x, y) || collide("EnemigoInofensivo", x, y) || !tiempoVida || ((speed.x == 0) && (speed.y == 0)))
                    world.remove(this);
                if (collide("Solid", x + 1, y) ||
                    collide("Solid", x - 1, y) ||
                    collide("Solid", x, y + 1) ||
                    collide("Solid", x, y - 1))
                    world.remove(this);
            }
                
			tiempoVida--;
		}
		
        /**
         * obtenerCartesianas
         * Transforma un vector de la forma polar a cartesiana
         */
		public function obtenerCartesianas(_velocidadMod:Number, _velocidadArg:Number):Point {
            var vector:Point = new Point(0, 0);
            
            //transformamos el argumento, dado en grados, a radianes:
            _velocidadArg = (_velocidadArg * Math.PI) / 180;
            
            //obtenemos la forma binomial:
            vector.x = _velocidadMod * Math.cos(_velocidadArg);
            vector.y = _velocidadMod * Math.sin(_velocidadArg);
            
            //truncamos a dos decimales las coordenadas y le cambiamos el signo porque en informática
            //el eje Y está invertido en lugar de ser como los ejes cartesianos de toda la puta vida:
            vector.x =  int(vector.x * 100) / 100;
            vector.y = -int(vector.y * 100) / 100;
            
            return vector;
		}
	}
}












//